package com.apes.scm.account.account.service;

import com.apes.framework.api.DomainService;
import com.apes.framework.plugin.esb.api.SimpleRequest;
import com.apes.scm.account.account.model.InventoryBatch;
import com.apes.scm.account.account.model.InventoryConsign;
import com.apes.scm.account.account.repository.InventoryConsignRepository;
import com.apes.scm.account.method.Batch;
import com.apes.scm.masterdata.party.model.PartyRole;
import com.apes.scm.masterdata.product.model.Product;
import com.apes.scm.masterdata.product.model.ProductUom;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.stereotype.Service;

import java.util.*;
import java.util.function.Function;
import java.util.stream.Collectors;

/**
 * 功能：客户寄售库存服务
 *
 * @author xul
 * @create 2018-03-14 13:47
 */
@Service
public class InventoryConsignService extends DomainService {

    @Autowired
    InventoryConsignRepository inventoryConsignRepository;

    /**
     * 功能：保存寄售库存
     */
    public InventoryConsign save(InventoryConsign inventoryConsign) {
        return inventoryConsignRepository.saveAndFlush(inventoryConsign);
    }

    /**
     * 功能：批量保存寄售库存
     */
    public List<InventoryConsign> save(Iterable<InventoryConsign> inventoryConsigns) {
        return inventoryConsignRepository.save(inventoryConsigns);
    }

    public List<InventoryConsign> findInventoryConsignForOrder(PartyRole company, PartyRole customer, Product product, double priceUnit) {
        return inventoryConsignRepository.findInventoryConsignForOrder(company, customer, product, priceUnit);
    }

    public List<InventoryConsign> findInventoryConsignForReturn(PartyRole company, PartyRole customer, Product product, double priceUnit) {
        return inventoryConsignRepository.findInventoryConsignForReturn(company, customer, product, priceUnit);
    }

    public Integer getMaxBatchSerial(InventoryConsign oldBatch) {
        return inventoryConsignRepository.findMaxBatchSerial(oldBatch.getBatchNumber());
    }

    /**
     * 客户寄售：增加客户寄售库存
     */
    public void consign(Iterable<InventoryConsign> inventoryConsigns) {
        save(inventoryConsigns);
    }

    /**
     * 客户寄售退回：减少客户寄售库存
     */
    public void returns(Iterable<InventoryConsign> inventoryConsigns) {
        save(inventoryConsigns);
    }


    public Collection<Batch> wrapBatch(List<InventoryConsign> inventories, ProductUom toUom, Function<InventoryConsign, Double> function) {
        return inventories.stream()
                .filter(inventoryConsign -> function.apply(inventoryConsign) > 0)
                .map(inventoryConsign -> {
                    Batch batch = new Batch();
                    batch.setEntity(inventoryConsign);
                    batch.setQty(inventoryConsign.getUom().computeQty(function.apply(inventoryConsign), toUom, true));
                    return batch;
                }).collect(Collectors.toList());
    }


    /*
    * 查找对账批次
    * 消耗/退回
    * */
    public Page<Map<String,Object>> findForStatement(SimpleRequest request) {
        String companyId = request.get("companyId");
        String customerId = request.get("customerId");
        boolean returned = request.get("returned");
        Date startDate = request.get("startDate");
        Date endDate = request.get("endDate");
        Page<Map<String,Object>> result = null;
        if(returned) {
            result = inventoryConsignRepository.findInventoryConsignForReturn(companyId,customerId,startDate,endDate,PageRequest.of(request.get("page"), request.get("size")));
        }else {
            result = inventoryConsignRepository.findInventoryConsignForConsume(companyId,customerId,startDate,endDate,PageRequest.of(request.get("page"), request.get("size")));
        }
        if(!result.hasContent())  throw new RuntimeException("未找到待对账单据！");
        return result;
    }

}
